package edu.pku.sei.transformation.editor.controller.commands.link;

import edu.pku.sei.modeler.exceptions.FactoryNotFoundException;
import edu.pku.sei.modeler.model.common.ModelRegistry;
import edu.pku.sei.modeler.model.structure.MetaBendPoint;
import edu.pku.sei.modeler.model.structure.MetaLink;
import edu.pku.sei.modeler.model.structure.MetaNode;
import edu.pku.sei.modeler.model.structure.StructureFactory;

public class LinkCreateCommand extends
		AbstractLinkCreateCommand<MetaLink, MetaNode, MetaNode> {
	protected AbstractLinkCreateCommand modelCmd;

	public AbstractLinkCreateCommand getModelCmd() {
		return modelCmd;
	}

	public void setModelCmd(AbstractLinkCreateCommand modelCmd) {
		this.modelCmd = modelCmd;
	}

	public LinkCreateCommand(MetaLink newObj, MetaNode src) {
		super(newObj, src);
	}

	public LinkCreateCommand(MetaLink newObj, MetaNode src,
			AbstractLinkCreateCommand cmd) {
		this.link = newObj;
		this.source = src;
		this.modelCmd = cmd;
		super.setLabel(modelCmd.getLabel());
	}

	public boolean canExecute() {
		if (modelCmd != null && modelCmd.canExecute())
			return super.canExecute();
		return false;
	}

	public void execute() {
		if (source == target) {
			StructureFactory sFactory;
			try {
				sFactory = (StructureFactory) ModelRegistry.getRegistry()
						.getStructureFactory(link.getModelElement().getModel());
				MetaBendPoint p = sFactory.createMetaBendPoint();
				MetaBendPoint p1 = sFactory.createMetaBendPoint();
				MetaBendPoint p2 = sFactory.createMetaBendPoint();
				MetaBendPoint p3 = sFactory.createMetaBendPoint();
				p.x = source.getLocationX();
				p.y = source.getLocationY();

				p1.x = p.x - 10;
				p1.y = p.y + 10;
				p2.x = p.x - 10;
				p2.y = p.y - 10;
				p3.x = p.x + 10;
				p3.y = p.y - 10;

				link.getBendPoints().add(p1);
				link.getBendPoints().add(p2);
				link.getBendPoints().add(p3);
			} catch (IllegalArgumentException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (FactoryNotFoundException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
		if (modelCmd != null && !link.isReferenceShape())
			modelCmd.execute();

		// FIXME: This statement has an non-local-handled exception
		link.setSource(source);
		source.getOutgoings().add(link);
		link.setTarget(target);
		target.getIncomings().add(link);
		link.setContainer(source);
		// link.setModel(source.getModel());
		// source.getDiagram().getConnections().add(link);
	}

	public void undo() {
		link.setSource(null);
		link.setTarget(null);
		if (source == target) {
			link.getBendPoints().clear();
		}
		if (modelCmd != null)
			modelCmd.undo();
	}
}
